package module

import (
	"encoding/json"
	"github.com/go-chi/chi"
	"github.com/go-chi/cors"
	"net/http"
	"strconv"
)

type module struct {
	Router chi.Router
}

func NewModule(router chi.Router)*module  {
	return &module{Router:router}
}

func (m *module)Start()error  {
	cors := cors.New(cors.Options{
		AllowedOrigins:   []string{"*"},
		AllowedMethods:   []string{"GET", "POST", "PUT", "DELETE", "OPTIONS"},
		AllowedHeaders:   []string{"Accept", "Content-Type", "Authorization"},
		AllowCredentials: true,
		Debug:            true,
	})
	m.Router.Route("/", func(r chi.Router) {
		r.Use(cors.Handler)
		//容器
		r.Route("/con", func(r chi.Router) {
			r.Post("/create", func(writer http.ResponseWriter, request *http.Request) {
				if err:=ConCreate(request);err!=nil{
					m.presentError(writer,err)
				}else {
					m.encode(writer,nil)
				}
			})
			r.Post("/version/{dname}/{cname}/{img}", func(writer http.ResponseWriter, request *http.Request) {
				dname:= func(rq *http.Request)string {
					return chi.URLParam(rq,"dname")
				}
				cname:= func(rq *http.Request)string {
					return chi.URLParam(rq,"cname")
				}
				img:= func(rq *http.Request)string {
					return chi.URLParam(rq,"img")
				}
				if err:=ConVersion(dname(request),cname(request),img(request));err!=nil{
					m.presentError(writer,err)
				}else {
					m.encode(writer,nil)
				}
			})
			r.Post("/replicas/{name}/{count}", func(writer http.ResponseWriter, request *http.Request) {
				name:= func(rq *http.Request)string {
					return chi.URLParam(rq,"name")
				}
				count:= func(rq *http.Request)string {
					return chi.URLParam(rq,"count")
				}
				if err:=Conreplicas(name(request),count(request));err!=nil{
					m.presentError(writer,err)
				}else {
					m.encode(writer,nil)
				}

			})
			r.Put("/replace/{id}", func(writer http.ResponseWriter, request *http.Request) {
				id:= func(rq *http.Request)string {
					return chi.URLParam(rq,"id")
				}
				if err:=ConReplace(id(request),request);err!=nil{
					m.presentError(writer,err)
				}else {
				//	writer.WriteHeader(http.StatusOK)
					m.encode(writer,nil)
				}
			})
			r.Get("/allcon/{pn}/{eg}", func(writer http.ResponseWriter, request *http.Request) {
				//调用所有容器组方法
				//var page Page
				//json.NewDecoder(request.Body).Decode(&page)
				var page Page
				pn:= func(rq *http.Request)string {
					return chi.URLParam(rq,"pn")
				}
				eg:= func(rq *http.Request)string {
					return chi.URLParam(rq,"eg")
				}
				pnint,_:=strconv.Atoi(pn(request))
				egint,_:=strconv.Atoi(eg(request))
				page.PageNumber=pnint
				page.EveryPage=egint
				m.encode(writer,ConFindAll(page))
			})
			r.Post("/fuzzy", func(writer http.ResponseWriter, request *http.Request) {
				//调用指定容器组
				var fuzzy Fuzzy
				json.NewDecoder(request.Body).Decode(&fuzzy)
				m.encode(writer,ConFuzzy(fuzzy))
			})
			r.Route("/name/{id}", func(r chi.Router) {
				id:= func(rq *http.Request)string {
					return chi.URLParam(rq,"id")
				}
				r.Delete("/", func(writer http.ResponseWriter, request *http.Request) {
					if err:=ConDel(id(request));err!=nil{
						m.presentError(writer,err)
					}else {
						m.encode(writer,nil)
					}
				})
			})
		})
		//服务
		r.Route("/svc", func(r chi.Router) {
			r.Post("/create", func(writer http.ResponseWriter, request *http.Request) {
				//var data interface{}
				//yaml.NewDecoder(request.Body).Decode(data)
				//s,_:=ioutil.ReadAll(request.Body)
				//fmt.Println("ssssssssssssssss",s)

				if err:=SvcCreate(request);err!=nil{
					m.presentError(writer,err)
				}else {
					m.encode(writer,nil)
				}
			})
			r.Get("/allsvc/{pn}/{eg}", func(writer http.ResponseWriter, request *http.Request) {
				//调用所有容器组方法
				//SvcFindAll()
				var page Page
				pn:= func(rq *http.Request)string {
					return chi.URLParam(rq,"pn")
				}
				eg:= func(rq *http.Request)string {
					return chi.URLParam(rq,"eg")
				}
				pnint,_:=strconv.Atoi(pn(request))
				egint,_:=strconv.Atoi(eg(request))
				page.PageNumber=pnint
				page.EveryPage=egint
				m.encode(writer,SvcFindAll(page))
			})
			r.Post("/fuzzy", func(writer http.ResponseWriter, request *http.Request) {
					var fuzzy Fuzzy
					json.NewDecoder(request.Body).Decode(&fuzzy)
					m.encode(writer,SvcFuzzy(fuzzy))
			})
			r.Route("/name/{id}", func(r chi.Router) {
				id:= func(rq *http.Request)string {
					return chi.URLParam(rq,"id")
				}
				r.Delete("/", func(writer http.ResponseWriter, request *http.Request) {
					if err:=SvcDel(id(request));err!=nil{
						m.presentError(writer,err)
					}else {
						m.encode(writer,nil)
					}

				})
			})
		})
	})


	return nil
}

func (m *module)Stop()  {

}

func (m *module) presentError(w http.ResponseWriter, err error) {
	w.Header().Set("Content-Type", "application/json; charset=utf-8")
	switch err {
	//case internal.ErrAgentAlreadyExists:
	//	w.WriteHeader(http.StatusBadRequest)
	//case internal.ErrAgentNotFound:
	//	w.WriteHeader(http.StatusNotFound)
	default:
		w.WriteHeader(http.StatusNotFound)
		return // no externalisation of internal errors
	}

	m.encode(w, &struct{ Error string `json:"error"` }{Error: err.Error()})
}

func (m *module)encode(writer http.ResponseWriter,data interface{})  {
	//writer.Header().Set("Access-Control-Allow-Origin","*")
	//writer.Header().Add("Access-Control-Allow-Headers","Content-Type")
	writer.WriteHeader(http.StatusOK)
	writer.Header().Set("Content-type","application/json; charset=utf-8")
	encoder:=json.NewEncoder(writer)
	encoder.SetIndent("", "  ")
	if err:=encoder.Encode(data);err!=nil{
		//do nothing
	}
}